package infomap

class UsuarioController {

    static allowedMethods = [save: "POST", update: "POST", delete: "POST"]
    def beforeInterceptor = [action: this.&checkUser, except: ["create","save","login","doLogin"]]

    def checkUser(){
        if(!session.user) {
            redirect(controller:'usuario',action:'login')
            return false
        }
    }

    def index = {
        redirect(action: "list", params: params)
    }

    def list = {
        params.max = Math.min(params.max ? params.int('max') : 10, 100)
        [usuarioInstanceList: Usuario.list(params), usuarioInstanceTotal: Usuario.count()]
    }

    def create = {
        def usuarioInstance = new Usuario()
        usuarioInstance.properties = params


        return [usuarioInstance: usuarioInstance]
    }

    def save = {
        def usuarioInstance = new Usuario(params)
        def planes = []
        if (params.plan in String){
            planes << params.plan
        } else {
            planes = params.plan
        }
        planes.each {
            usuarioInstance.addToPlanes(Plan.get(it))
        }
        if (usuarioInstance.save(flush: true)) {
            session.user = usuarioInstance
            flash.message = "Usuario creado correctamente"
            redirect(action: "show", id: usuarioInstance.id)
        }
        else {
            render(view: "create", model: [usuarioInstance: usuarioInstance])
        }
    }

    def show = {
        def usuarioInstance = Usuario.get(params.id)
        if (!usuarioInstance) {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
        else {
            [usuarioInstance: usuarioInstance]
        }
    }

    def edit = {
        def usuarioInstance = Usuario.get(params.id)
        if (!usuarioInstance) {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
        else {
            return [usuarioInstance: usuarioInstance]
        }
    }

    def update = {
        def usuarioInstance = Usuario.get(params.id)
        if (usuarioInstance) {
            if (params.version) {
                def version = params.version.toLong()
                if (usuarioInstance.version > version) {
                    
                    usuarioInstance.errors.rejectValue("version", "default.optimistic.locking.failure", [message(code: 'usuario.label', default: 'Usuario')] as Object[], "Another user has updated this Usuario while you were editing")
                    render(view: "edit", model: [usuarioInstance: usuarioInstance])
                    return
                }
            }

            if (params.services){
                def servicios = []
                if (params.services in String){
                    servicios << (params.services as Long)
                } else {
                    servicios = params.services.collect { it as Long }
                }

                def allIds = usuarioInstance.servicios*.id
                def deletedIds = allIds - servicios
                println "******* deleted $deletedIds"
                deletedIds.each { deletedId ->
                    def service = usuarioInstance.servicios.find { it.id == deletedId }
                    usuarioInstance.removeFromServicios(service)
                }

                def newIds = servicios - allIds
                println "******* newIds $newIds"
                newIds.each {
                    usuarioInstance.addToServicios(Servicio.get(it))
                }
            }

            if (params.zonas){
                def zonas = []
                if (params.zonas in String){
                    zonas << (params.zonas as Long)
                } else {
                    zonas = params.zonas.collect { it as Long }
                }

                def allIds = usuarioInstance.zonas*.id
                def deletedIds = allIds - zonas
                deletedIds.each { deletedId ->
                    def service = usuarioInstance.zonas.find { it.id == deletedId }
                    usuarioInstance.removeFromZonas(service)
                }

                def newIds = zonas - allIds
                newIds.each {
                    usuarioInstance.addToZonas(Zona.get(it))
                }
            }

            usuarioInstance.properties = params
            if (!usuarioInstance.hasErrors() && usuarioInstance.save(flush: true)) {
                flash.message = "${message(code: 'default.updated.message', args: [message(code: 'usuario.label', default: 'Usuario'), usuarioInstance.id])}"
                redirect(action: "show", id: usuarioInstance.id)
            }
            else {
                render(view: "edit", model: [usuarioInstance: usuarioInstance])
            }
        }
        else {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
    }

    def delete = {
        def usuarioInstance = Usuario.get(params.id)
        if (usuarioInstance) {
            try {
                usuarioInstance.delete(flush: true)
                flash.message = "${message(code: 'default.deleted.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
                redirect(action: "list")
            }
            catch (org.springframework.dao.DataIntegrityViolationException e) {
                flash.message = "${message(code: 'default.not.deleted.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
                redirect(action: "show", id: params.id)
            }
        }
        else {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
    }

    def login = {
        if (session.user)
            redirect(controller:"map")
    }

    def doLogin = {
        def user = Usuario.findWhere(mail:params['email'], password:params['password'])
        session.user = user
        if (user)
              redirect(controller:'map')
           else
              redirect(controller:'usuario',action:'login')

    }

    def logout = {
        session.user = null
        redirect(controller:'map')
    }

    def editServicios = {
        Usuario usuarioInstance = Usuario.get(session.user.id)


        if (!usuarioInstance) {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
        else {
            def serviciosContenidos = Servicio.list().collect { usuarioInstance.servicios.contains(it) ? "checked" : "" }

            return [usuarioInstance: usuarioInstance, serviciosContenidos: serviciosContenidos]
        }
    }

    def editZonas = {
        Usuario usuarioInstance = Usuario.get(session.user.id)
        if (!usuarioInstance) {
            flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'usuario.label', default: 'Usuario'), params.id])}"
            redirect(action: "list")
        }
        else {
            def zonasContenidos = Zona.list().collect { usuarioInstance.zonas.contains(it) ? "checked" : "" }

            return [usuarioInstance: usuarioInstance, zonasContenidos: zonasContenidos]
        }
    }

     def listRecorridos = {
        Usuario usuarioInstance = Usuario.get(session.user.id)
        params.max = Math.min(params.max ? params.int('max') : 10, 100)
        def recorridos = []
        Recorrido.list(params).each{
            if(usuarioInstance.recorridos.contains(it)) {
                recorridos.add(it)
            }
        }
        [recorridosList: recorridos, recorridosTotal: usuarioInstance.recorridos.size(), usuarioInstance: usuarioInstance]

    }

    def createRecorrido = {

    }

    def saveRecorrido = {
        def usuarioInstance = Usuario.get(session.user.id)
        def recorrido = new Recorrido(nombre: params.nombre, origen: params.origen, destino: params.destino)

        if (params.puntosIntermedios){
            params.puntosIntermedios.each {
                def puntos = it.replace("(","").replace(")","").replace(",", " ")
                def coords = puntos.split()

                def ubicacion = new Ubicacion(latitud: coords[0], longitud: coords[1])
                ubicacion.save(flush: true)
                recorrido.addToPuntosIntermedios(ubicacion)
            }
        }

        usuarioInstance.addToRecorridos(recorrido)

        if (usuarioInstance.save(flush: true)) {
            session.user = usuarioInstance
            flash.message = "Recorrido creado correctamente."
            redirect(action: "listRecorridos")
        } else {
            flash.message = "El recorrido no se pudo crear."
            redirect(action: "createRecorrido")
        }

    }

    def showRecorrido = {
        def usuarioInstance = Usuario.get(session.user.id)
        def recorrido = Recorrido.get(params.id)
        if (!recorrido) {
            flash.message = "Recorrido con id "+ params.id + " no encontrado."
            redirect(action: "listRecorridos")
        }
        else {
            return [recorrido: recorrido, usuarioInstance: usuarioInstance]
        }
    }

    def deleteRecorrido = {
        def usuarioInstance = Usuario.get(session.user.id)
        def recorrido = Recorrido.get(params.id)
        if (!recorrido) {
            flash.message = "Recorrido con id "+ params.id + " no encontrado."
            redirect(action: "listRecorridos")
        } else {
            usuarioInstance.removeFromRecorridos(recorrido)
            recorrido.delete()
            flash.message = "Recorrido eliminado."
            redirect(action: "listRecorridos")
        }
    }

}
